package galaxy.app.system;

import java.io.File;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;

import com.alibaba.fastjson.JSONObject;

import galaxy.app.Galaxy;
import galaxy.app.common.NodeInfo;
import galaxy.app.log.LogHelper;
import galaxy.kernel.Constants;
import galaxy.kernel.system.AbstractECSSystem;
import galaxy.kernel.utils.JsonUtils;
import galaxy.kernel.utils.PathUtils;

public class ConfigSystem extends AbstractECSSystem {

    ConfigComponent c;

    public ConfigSystem(String configPath, String envDir, String envName, String nodeId){
        c = Galaxy.components().getSingle(ConfigComponent.class);
        c.rootConfigPath = configPath;
        c.envDir = envDir;
        c.envName = envName;
        c.nodeId = nodeId;

        if (c.rootConfigPath == null || c.envDir == null || c.envName == null || c.nodeId == null) {
            StringBuilder sb = new StringBuilder();
            sb.append("galaxy VM options config error...\n");
            sb.append("-Dgalaxy.config      \t 配置文件相对根路径.  eg. -Dgalaxy.config=config \n");
            sb.append("-Dgalaxy.env         \t运行环境名称.  eg. -Dgalaxy.env=local \n");
            sb.append("-Dgalaxy.nodeid      \t当前服务器的结点id.  eg. -Dgalaxy.nodeid=gate-1 \n");
            try {
                throw new Exception(sb.toString());
            } catch (Exception e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }

        //check env path
        File path = new File(getEnvPath());
        if (!path.isDirectory()) {
            try {
                throw new Exception(String.format("file:%s  is not directory.", getEnvPath()));
            } catch (Exception e) {
                // TODO Auto-generated catch block
                e.printStackTrace();
            }
        }
    }

    public String getEnvPath() {
        return PathUtils.combine(c.rootConfigPath, c.envDir, c.envName);
    }

    @Override
    public void load(){
        //init logback.xml configure
        String logbackPath = Paths.get(getEnvPath(), Constants.File.LOG_BACK).toString();   
        loadLogConfig(logbackPath);

        LogHelper.info("========== node launcher ==========");
        LogHelper.info("nodeId:{}, configPath:{}, envName:{}", c.nodeId, c.rootConfigPath, c.envName);

        loadAppConfig();
        loadNodesConfig();
    }

    // @Override
    // public void start() {
        
    // }

    protected void loadLogConfig(String logbackPath){
		// 初始化日志配置
		// String logbackdir = configdir + File.separator + logback;
		System.setProperty("logback.configurationFile", logbackPath);
		System.setProperty("logback.configurationFile_bak", logbackPath);
		LogHelper.initLog();
	}
     /**
     * read app.json
     */
    private void loadAppConfig() {
        c.appConfig = JsonUtils.read(getEnvPath(), Constants.File.APP_DOT_JSON);
        //start BasePackage
        c.basePackages = JsonUtils.readStringArray(c.appConfig, Constants.Component.BASE_PACKAGES);
        c.debug = c.appConfig.getBoolean("debug");
    }

    /**
     * read nodes.json
     */
    private void loadNodesConfig()  {
        JSONObject jsonObject = JsonUtils.read(getEnvPath(), Constants.File.NODES_DOT_JSON);
        c.nodesInfo.putAll(NodeInfo.getNodeMaps(jsonObject, c.nodeId));

        for (List<NodeInfo> list : c.nodesInfo.values()) {
            for (NodeInfo si : list) {
                if (si.getNodeId().equals(c.nodeId)) {
                    c.currentNode = si;
                }
            }
        }

        if (c.currentNode == null) {
            List<String> idList = new ArrayList<>();
            for (List<NodeInfo> list : c.nodesInfo.values()) {
                for (NodeInfo serverInfo : list) {
                    idList.add(serverInfo.getNodeId());
                }
            }

            try {
                throw new Exception(String.format("can not found current node. nodeId=%s, %s", c.nodeId, idList));
            } catch (Exception e) {
                // TODO Auto-generated catch block
                LogHelper.error("{}",e);
            }
        }
    }
}
